<script lang="ts" setup>
import { getCourseInformationById, getSourceFileUrlApi, updateCourseStudyRecordApi } from '@/api/study/course';
import { useFileTransStore } from '@/stores/fileTransStore';
import { useStudyRecordStore } from '@/stores/studyRecordStore';
import { SearchOutlined } from '@ant-design/icons-vue';
import { message } from 'ant-design-vue';
import { storeToRefs } from 'pinia';
import { nextTick, onBeforeMount, onMounted, reactive, ref, watch } from 'vue';
import vue3videoPlay from 'vue3-video-play'; // 导入 vue3-video-play 组件
import 'vue3-video-play/dist/style.css'; // 引入样式文件
interface Comment {
  avatar: string;
  username: string;
  timestamp: string;
  text: string;
  startTime: number;
}

const props = defineProps({
  courseId: {
    type: String,
    required: true,
  },
  sourceId: {
    type: String,
    required: true,
  },
});

const isPlaying = ref(false);
const searchText = ref<string>('');
const matchingIndexes = ref<number[]>([]);
const currentMatchIndex = ref<number>(0);
const playerRef = ref<any>(null); // 定义播放器引用
const fileTransStore = useFileTransStore();
const { transcription } = storeToRefs(fileTransStore);
const sourceFileUrl = ref<string | null>(null);
const studyRecordStore = useStudyRecordStore();
const courseName = ref<string>('');
const options = reactive({
  width: "90%", // 播放器宽度
  height: "450px", // 播放器高度
  color: "#409eff", // 主题色
  title: "", // 视频名称
  src: sourceFileUrl, // 视频源
  muted: false, // 静音
  webFullScreen: false,
  speedRate: ["0.75", "1.0", "1.25", "1.5", "2.0"], // 播放倍速
  autoPlay: false, // 自动播放
  loop: false, // 循环播放
  mirror: false, // 镜像画面
  ligthOff: false, // 关灯模式
  volume: 0.3, // 默认音量大小
  control: true, // 是否显示控制
  controlBtns: [
    "audioTrack",
    "quality",
    "speedRate",
    "volume",
    "setting",
    "pip",
    "pageFullScreen",
    "fullScreen",
  ], // 显示所有按钮,
});

// 定时器
let timer: any | null = null;
let watchTime = 0;
// 发送学习记录
const sendStudyRecord = async () => {
  try {
    const response = await updateCourseStudyRecordApi(props.sourceId);
    studyRecordStore.setStudyRecordData(response);
    watchTime = 0;
  }
  catch (error) {
    message.error("发送学习记录失败");
  }
};

// 播放器开始播放时触发发送学习记录
const startTimer = () => {
  sendStudyRecord();
  timer = setInterval(() => {
    watchTime += 1;
    if (watchTime % 60 === 0)
      sendStudyRecord();
  }, 1000);
};

// 停止计时
const stopTimer = () => {
  if (timer) {
    clearInterval(timer);
    timer = null;
  }
};

// 获取课程名称
const fetchCourseName = async () => {
  try {
    const response = await getCourseInformationById(props.courseId);
    courseName.value = response.courseName;
  }
  catch (error) {
    message.error("获取课程元信息失败");
  }
};

// 获取具体资源URL
const fetchSourceFileInfo = async (sourceId: string) => {
  try {
    const response = await getSourceFileUrlApi(sourceId);
    sourceFileUrl.value = response;

    // 更新播放器数据源
    if (playerRef.value) {
      const videoElement = playerRef.value.$el.querySelector('video') as HTMLVideoElement | null;
      if (videoElement) {
        videoElement.src = response;
        videoElement.load();

        // 监听 loadedmetadata 事件，确保视频元数据加载完成
        videoElement.addEventListener('loadedmetadata', () => {
          // 视频元数据加载完成
        });
      }
      else {
        message.error("视频元素未找到。");
      }
    }
  }
  catch (error) {
    message.error("获取资源信息失败");
  }
};

// 监听 props.sourceId 的变化，更新资源 URL
watch(() => props.sourceId, (newSourceId: string) => {
  fetchSourceFileInfo(newSourceId);
});

// 用于显示的评论数据
const comments = ref<Comment[]>([]);

// 从 transcription 中提取评论数据
const updateComments = () => {
  comments.value = transcription.value?.Paragraphs?.map((paragraph: any) => {
    const text = paragraph.Words.map((word: any) => word.Text).join('');
    const startTime = paragraph.Words[0].Start / 1000;
    const timestamp = `${Math.floor(paragraph.Words[0].Start / 60000)}:${((paragraph.Words[0].Start % 60000) / 1000).toFixed(0).padStart(2, '0')}`;
    return {
      avatar: '@/assets/729.png',
      username: `发言人${paragraph.SpeakerId}`,
      timestamp,
      text,
      startTime,
    };
  }) || [];
};

// 监听 transcription 的变化
watch(transcription, () => {
  updateComments(); // 更新评论数据
}, { immediate: true });

// 初始化时获取资源信息、评论数据和课程名称
onMounted(() => {
  fetchSourceFileInfo(props.sourceId);
  startTimer();
  fetchCourseName();

  // 确保在下一个 tick 中获取播放器实例
  nextTick(() => {
    if (playerRef.value) {
      const videoElement = playerRef.value.$el.querySelector('video') as HTMLVideoElement | null;
      if (videoElement) {
        // 播放器实例已获取
      }
      else {
        // 视频元素未准备好
      }
    }
    else {
      // PlayerRef 未设置
    }
  });

  // 初始化获取评论数据和课程名称
  updateComments();
  fetchCourseName();
});

// 组件销毁前清理
onBeforeMount(() => {
  stopTimer();
  // 超过40秒也算一次发送学习记录
  if (watchTime > 40)
    sendStudyRecord();
});

// 定位到指定时间并播放
const seekAndPlay = (time: number) => {
  if (playerRef.value) {
    const videoElement = playerRef.value.$el.querySelector('video') as HTMLVideoElement | null;
    if (videoElement) {
      try {
        videoElement.currentTime = time; // 使用 currentTime 定位
        videoElement.play(); // 播放视频
        isPlaying.value = true;
      }
      catch (error) {
        message.error("视频定位失败");
      }
    }
    else {
      message.error("视频播放器未准备好");
    }
  }
  else {
    message.error("视频播放器未准备好");
  }
};

// 滚动到评论卡片并定位视频
const scrollToCard = (index: number) => {
  const comment = comments.value[index];
  if (comment) {
    const card = document.getElementsByClassName('comment')[index] as HTMLElement;
    if (card) {
      card.scrollIntoView({ behavior: 'smooth', block: 'center' });
      seekAndPlay(comment.startTime);
    }
    else {
      message.error("评论卡片元素未找到。");
    }
  }
  else {
    message.error("未找到对应的评论。");
  }
};

const handleSearch = () => {
  const matches = comments.value
    .map((comment, index) => (comment.text.includes(searchText.value) ? index : -1))
    .filter(index => index !== -1);

  if (matches.length) {
    matchingIndexes.value = matches;
    currentMatchIndex.value = 0;
    scrollToCard(matches[0]);
  }
  else {
    matchingIndexes.value = [];
    message.info("未找到匹配的评论。");
  }
};

const handleCardClick = (index: number) => {
  scrollToCard(index);
};

const handlePreviousMatch = () => {
  if (currentMatchIndex.value > 0) {
    currentMatchIndex.value -= 1;
    const prevIndex = matchingIndexes.value[currentMatchIndex.value];
    scrollToCard(prevIndex);
  }
  else {
    message.info("已到达第一个匹配项。");
  }
};

const handleNextMatch = () => {
  if (currentMatchIndex.value < matchingIndexes.value.length - 1) {
    currentMatchIndex.value += 1;
    const nextIndex = matchingIndexes.value[currentMatchIndex.value];
    scrollToCard(nextIndex);
  }
  else {
    message.info("已到达最后一个匹配项。");
  }
};

const highlightText = (text: string, search: string) => {
  if (!search)
    return text;
  const regex = new RegExp(`(${search})`, 'gi');
  const highlighted = text.replace(regex, `<span style="background-color: yellow;">$1</span>`);
  return highlighted;
};
</script>

<template>
  <div class="container">
    <!-- 标题部分 -->
    <div style="display: flex; align-items: center; justify-content: space-between;">
      <div style="margin-left: 4rem;">
        <h2>
          {{ courseName }}
        </h2>
      </div>

      <!-- 搜索部分 -->
      <div class="header">
        <div>
          <a-input
            v-model:value="searchText"
            placeholder="搜索内容..."
            @press-enter="handleSearch"
          >
            <template #prefix>
              <SearchOutlined />
            </template>
            <template #addonAfter>
              <div style="display:flex;flex-direction: row;justify-content: center;">
                <div style="margin-top: 0px;margin-right: 10px;">
                  <span class="pageItem" @click="handlePreviousMatch">‹</span>
                  <span class="pageItem">
                    {{ matchingIndexes.length > 0 ? `${currentMatchIndex + 1}/${matchingIndexes.length}` : '0/0' }}
                  </span>
                  <span class="pageItem" @click="handleNextMatch">›</span>
                </div>
                <a-button style="border:none;height:100%;" @click="searchText = ''">
                  取消
                </a-button>
              </div>
            </template>
          </a-input>
        </div>
      </div>
    </div>

    <!-- 视频播放部分 -->
    <div class="videoContainer">
      <vue3videoPlay ref="playerRef" class="vjs-custom-skin" :options="options" :src="options.src" />
    </div>

    <!-- 评论部分 -->
    <div class="commentSection">
      <div
        v-for="(comment, idx) in comments"
        :key="idx"
        class="comment comment-clickable"
        @click="handleCardClick(idx)"
      >
        <div class="commentHeader">
          <img src="@/assets/729.png" alt="avatar" class="avatar">
          <span class="username">{{ comment.username }}</span>
          <span class="timestamp">{{ comment.timestamp }}</span>
          <div class="icons">
            <a-button class="iconButton">
              <img src="@/assets/836.png" alt="Like" style="width: 24px; height: 24px;">
            </a-button>
            <a-button class="iconButton">
              <img src="@/assets/844.png" alt="Dislike" style="width: 24px; height: 24px;">
            </a-button>
            <a-button class="iconButton">
              <img src="@/assets/851.png" alt="Copy" style="width: 24px; height: 24px;">
            </a-button>
            <a-button class="iconButton">
              <img src="@/assets/858.png" alt="Comment" style="width: 24px; height: 24px;">
            </a-button>
          </div>
        </div>
        <div class="commentText" v-html="highlightText(comment.text, searchText)" />
      </div>
    </div>
  </div>
</template>

<style scoped>
/* CSS Reset */
* {
  margin: 0;
  padding: 0;
  box-sizing: border-box;
}

body {
  font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
  font-size: 16px;
  line-height: 1.6;
  background-color: #ffffff;
  color: #333;
}

.container {
  background-color: #ffffff;
  padding: 1.25rem; /* 使用 rem 单位 */
  border-radius: 8px;
  margin-left: -30px;
  max-height: 100vh;

}

.header {
  display: -webkit-flex;
  display: -ms-flexbox;
  display: flex;
  flex-direction: column;
  -webkit-justify-content: space-between;
      -ms-flex-pack: justify;
          justify-content: space-between;
  -webkit-align-items: center;
      -ms-flex-align: center;
          align-items: center;
  margin-bottom: 6px;
  margin-top: 10px;
}

.headerLeft {
  -webkit-flex: 1;
      -ms-flex: 1;
          flex: 1;
}

.headerTitle {
  font-size: 18px;
  font-weight: normal;
  color: #3f3f3f;
  margin: 0;
}

.addButton {
  background: linear-gradient(135deg, rgba(0, 51, 153, 0.8) 0%, rgba(0, 51, 153, 0.5) 100%);
      box-shadow: 0 4px 10px rgba(0, 51, 153, 0.3);

  color: #fff;
  border-radius: 20px;
  border: none;
  cursor: pointer;
  padding: 10px 20px;
}

.headerRight {
  display: -webkit-flex;
  display: -ms-flexbox;
  display: flex;
  -webkit-align-items: center;
      -ms-flex-align: center;
          align-items: center;
  border-radius: 20px;
  padding: 5px 10px;
}

.searchInput {
  width: 200px;
  border: none;
  border-radius: 20px;
  background-color: transparent;
  margin-right: 20px;
  padding-left: 15px;
  height: 35px;
  outline: none;
}

.pagination {
  margin-right: 20px;
}

.pageItem {
  font-size: 18px;
  color: rgb(80, 74, 74);
  margin: 0 5px;
}

.cancelButton {
  background-color: transparent;
  color: rgb(80, 74, 74);
  border: none;
  cursor: pointer;
  font-size: 14px;
  height: 35px;
  padding: 0;
}

/* 竖线分隔 */
.headerRight > *:not(:last-child) {
  position: relative;
  padding-right: 20px;
  margin-right: 20px;
}

.headerRight > *:not(:last-child)::after {
  content: '';
  position: absolute;
  top: 50%;
  right: 0;
  width: 1px;
  height: 50%;
  background-color: #ddd;
  -webkit-transform: translateY(-50%);
      -ms-transform: translateY(-50%);
          transform: translateY(-50%);
}

.videoContainer {
  position: relative;
  margin-bottom: 16px;
}

.reactPlayer {
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
}

.commentSection {
  margin-top: 20px;
  overflow-x: hidden;
  height: calc(100vh - 658px);
  background-color: #ffffff;
  min-width: 800px;
}

.comment {
  background-color: #ffffff;
  padding: 12px;
  border-radius: 8px;
  margin-bottom: 12px;
  margin-left: 5px;
  margin-right: 15px;
}

.commentHeader {
  display: -webkit-flex;
  display: -ms-flexbox;
  display: flex;
  -webkit-align-items: center;
      -ms-flex-align: center;
          align-items: center;
  margin-bottom: 10px;
}

.avatar {
  width: 40px;
  height: 40px;
  border-radius: 50%;
  margin-right: 10px;
}

.username {
  font-weight: bold;
  margin-right: 10px;
  color: #333;
}

.timestamp {
  color: #888;
  margin-right: auto;
}

.icons {
  display: -webkit-flex;
  display: -ms-flexbox;
  display: flex;
  gap: 10px;
}

.iconButton {
  background-color: transparent;
  border: none;
  color: #333;
  font-size: 18px;
  padding: 0;
  cursor: pointer;
}

.commentText {
  padding: 12px;
  border-radius: 8px;
  margin-top: 10px;
  font-size: 14px;
  line-height: 1.6;
}

/* 奇数项的样式 */
.comment:nth-child(odd) .commentText {
  background: linear-gradient(135deg, rgba(0, 51, 153, 0.8) 0%, rgba(0, 51, 153, 0.5) 100%);
      box-shadow: 0 4px 10px rgba(0, 51, 153, 0.3);

  color: #fff;
}

/* 偶数项的样式 */
.comment:nth-child(even) .commentText {
  background-color: #ffffff;
  color: #333;
}

/* 响应式设计 */
@media (max-width: 600px) {
  .container {
    padding: 10px;
    max-width: 100%;
  }

  .header {
    -webkit-flex-direction: column;
        -ms-flex-direction: column;
            flex-direction: column;
    -webkit-align-items: flex-start;
        -ms-flex-align: start;
            align-items: flex-start;
  }

  .searchInput {
    width: 100%;
    margin-right: 0;
    margin-bottom: 10px;
  }

  .headerRight {
    -webkit-flex-direction: column;
        -ms-flex-direction: column;
            flex-direction: column;
    -webkit-align-items: flex-start;
        -ms-flex-align: start;
            align-items: flex-start;
  }

  .pagination {
    margin-right: 0;
  }
}
.audioPlayerContainer {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-top: 20px;
  padding: 10px;
  background: linear-gradient(135deg, rgba(0, 51, 153, 0.8) 0%, rgba(0, 51, 153, 0.5) 100%);
  border-radius: 12px;
  box-shadow: 0 4px 8px rgba(0, 0, 0, 0.2);
}

.reactPlayerCustom {
  border-radius: 12px;
  overflow: hidden;
  width: 100%;
}

.playPauseButton {
  margin-left: 15px;
  background-color: #ffffff;
  color: linear-gradient(135deg, rgba(0, 51, 153, 0.8) 0%, rgba(0, 51, 153, 0.5) 100%);
  border: none;
  padding: 10px 20px;
  border-radius: 20px;
  cursor: pointer;
  font-weight: bold;
  box-shadow: 0 2px 4px rgba(0, 0, 0, 0.2);
}

.playPauseButton:hover {
  background-color: linear-gradient(135deg, rgba(0, 51, 153, 0.8) 0%, rgba(0, 51, 153, 0.5) 100%);
  color: #ffffff;
}
</style>
